home *** CD-ROM | disk | FTP | other *** search
/ Graphics Plus / Graphics Plus.iso / general / convrtrs / pbmplus / hpcd2ppm.lha / hpcdtoppm.0.5.pl1 / src / tools.c < prev   
C/C++ Source or Header  |  1993-08-20  |  9KB  |  422 lines

  1. /* hpcdtoppm (Hadmut's pcdtoppm) v0.5pl1
  2. *  Copyright (c) 1992, 1993 by Hadmut Danisch (danisch@ira.uka.de).
  3. *  Permission to use and distribute this software and its
  4. *  documentation for noncommercial use and without fee is hereby granted,
  5. *  provided that the above copyright notice appear in all copies and that
  6. *  both that copyright notice and this permission notice appear in
  7. *  supporting documentation. It is not allowed to sell this software in 
  8. *  any way. This software is not public domain.
  9. */
  10.  
  11. #include "hpcdtoppm.h"
  12.  
  13.  
  14. void clearimpl(implane *l,sINT n)
  15. { dim x,y;
  16.   uBYTE *ptr;
  17.  
  18.   ptr=l->im;
  19.   for (x=0;x<l->mwidth;x++)
  20.     for (y=0; y<l->mheight;y++)
  21.       *(ptr++)=n;
  22. }
  23.  
  24.  
  25.  
  26.  
  27. void halve(implane *p)
  28.  {dim w,h,x,y;
  29.   uBYTE *optr,*nptr;
  30.  
  31.   melde("halve\n");
  32.   if ((!p) || (!p->im)) error(E_INTERN);
  33.  
  34.   w=p->iwidth/=2;      
  35.   h=p->iheight/=2;     
  36.  
  37.  
  38.   for(y=0;y<h;y++)
  39.    {
  40.     nptr=(p->im) +   y*(p->mwidth);
  41.     optr=(p->im) + 2*y*(p->mwidth);
  42.  
  43.     for(x=0;x<w;x++,nptr++,optr+=2)
  44.      { *nptr = *optr;
  45.      }
  46.  
  47.    }
  48.  
  49.  }
  50.  
  51.  
  52.  
  53.  
  54.  
  55.  
  56.  
  57. void interpolate(implane *p)
  58.  {dim w,h,x,y,yi;
  59.   uBYTE *optr,*nptr,*uptr;
  60.  
  61.   melde("interpolate\n");
  62.   if ((!p) || (!p->im)) error(E_INTERN);
  63.  
  64.   w=p->iwidth;
  65.   h=p->iheight;
  66.  
  67.   if(p->mwidth  < 2*w ) error(E_INTERN);
  68.   if(p->mheight < 2*h ) error(E_INTERN);
  69.  
  70.  
  71.   p->iwidth=2*w;
  72.   p->iheight=2*h;
  73.  
  74.  
  75.   for(y=0;y<h;y++)
  76.    {yi=h-1-y;
  77.     optr=p->im+  yi*p->mwidth + (w-1);
  78.     nptr=p->im+2*yi*p->mwidth + (2*w - 2);
  79.  
  80.     nptr[0]=nptr[1]=optr[0];
  81.  
  82.     for(x=1;x<w;x++)
  83.      { optr--; nptr-=2;
  84.        nptr[0]=optr[0];
  85.        nptr[1]=(((sINT)optr[0])+((sINT)optr[1])+1)>>1;
  86.      }
  87.     }
  88.  
  89.   for(y=0;y<h-1;y++)
  90.    {optr=p->im + 2*y*p->mwidth;
  91.     nptr=optr+p->mwidth;
  92.     uptr=nptr+p->mwidth;
  93.  
  94.     for(x=0;x<w-1;x++)
  95.      {
  96.       nptr[0]=(((sINT)optr[0])+((sINT)uptr[0])+1)>>1;
  97.       nptr[1]=(((sINT)optr[0])+((sINT)optr[2])+((sINT)uptr[0])+((sINT)uptr[2])+2)>>2;
  98.       nptr+=2; optr+=2; uptr+=2;
  99.      }
  100.     *(nptr++)=(((sINT)*(optr++))+((sINT)*(uptr++))+1)>>1;
  101.     *(nptr++)=(((sINT)*(optr++))+((sINT)*(uptr++))+1)>>1;
  102.    }
  103.  
  104.  
  105.   optr=p->im + (2*h-2)*p->mwidth;
  106.   nptr=p->im + (2*h-1)*p->mwidth;
  107.   for(x=0;x<w;x++)
  108.    { *(nptr++) = *(optr++);  *(nptr++) = *(optr++); }
  109.  
  110.  }
  111.  
  112.  
  113.  
  114.  
  115. static sINT testbegin(void)
  116.  {sINT i,j;
  117.   for(i=j=0;i<32;i++)
  118.     if(sbuffer[i]==0xff) j++;
  119.  
  120.   return (j>30);
  121.   
  122.  }
  123.  
  124.  
  125. sINT Skip4Base(void)
  126.  {sINT cd_offset,cd_offhelp;
  127.   
  128.   cd_offset = L_Head + L_Base16 + L_Base4 + L_Base ;
  129.   SEEK(cd_offset+3);          
  130.   EREADBUF;    
  131.   cd_offhelp=((((sINT)sbuffer[510])<<8)|sbuffer[511]) + 1;
  132.  
  133.   cd_offset+=cd_offhelp;
  134.  
  135.   SEEK(cd_offset);
  136.   EREADBUF;
  137.   while(!testbegin())
  138.    {cd_offset++;
  139.     EREADBUF;
  140.    }
  141.   return cd_offset;
  142.  }
  143.  
  144.  
  145.  
  146.  
  147.  
  148. void planealloc(implane *p, dim width, dim height)
  149.  {melde("planealloc\n");
  150.  
  151.   p->iwidth=p->iheight=0;
  152.   p->mwidth=width;
  153.   p->mheight=height;
  154.  
  155.   p->mp = ( p->im = ( uBYTE * ) malloc  (width*height*sizeof(uBYTE)) );
  156.   if(!(p->im)) error(E_MEM);
  157.  }
  158.  
  159.  
  160.  
  161. static void pastequer(implane *gross,dim px,dim py,implane *klein)
  162.  {dim x,y;
  163.   uBYTE *von,*nach;
  164.  
  165.   if(px+klein->iwidth  > gross->iwidth)  error(E_INTERN);
  166.   if(py+klein->iheight > gross->iheight) error(E_INTERN);
  167.  
  168.   for(y=0;y<klein->iheight;y++)
  169.    { von=klein->im + y * klein->mwidth;
  170.      nach=gross->im + (y+py) * gross->mwidth + px;
  171.      for(x=0;x<klein->iwidth;x++)
  172.         *(nach++)=*(von++);
  173.    }
  174.  }
  175.  
  176.  
  177. static void pastehead(implane *gross,dim px,dim py,implane *klein)
  178.  {dim x,y;
  179.   uBYTE *von,*nach;
  180.  
  181.   if(px+klein->iwidth  > gross->iwidth)  error(E_INTERN);
  182.   if(py+klein->iheight > gross->iheight) error(E_INTERN);
  183.  
  184.   for(y=0;y<klein->iheight;y++)
  185.    { von= klein->im + (klein->iheight-1-y) * klein->mwidth + (klein->iwidth - 1);
  186.      nach=gross->im + (y+py) * gross->mwidth + px;
  187.      for(x=0;x<klein->iwidth;x++)
  188.         *(nach++)=*(von--);
  189.    }
  190.  }
  191.  
  192.  
  193. static void pastelinks(implane *gross,dim px,dim py,implane *klein)
  194.  {dim x,y;
  195.   uBYTE *von,*nach;
  196.  
  197.   if(px+klein->iheight > gross->iwidth)  error(E_INTERN);
  198.   if(py+klein->iwidth  > gross->iheight) error(E_INTERN);
  199.  
  200.   for(y=0;y<klein->iwidth;y++)
  201.    { von=klein->im + klein->iwidth - 1 - y;
  202.      nach=gross->im + (y+py) * gross->mwidth + px;
  203.      for(x=0;x<klein->iheight;x++,von+=klein->mwidth)
  204.         *(nach++)=*(von);
  205.    }
  206.  }
  207.  
  208. static void pasterechts(implane *gross,dim px,dim py,implane *klein)
  209.  {dim x,y;
  210.   uBYTE *von,*nach;
  211.  
  212.   if(px+klein->iheight > gross->iwidth)  error(E_INTERN);
  213.   if(py+klein->iwidth  > gross->iheight) error(E_INTERN);
  214.  
  215.   for(y=0;y<klein->iwidth;y++)
  216.    { von=klein->im + (klein->iheight-1)*klein->mwidth + y;
  217.      nach=gross->im + (y+py) * gross->mwidth + px;
  218.      for(x=0;x<klein->iheight;x++,von-=klein->mwidth)
  219.         *(nach++)=*(von);
  220.    }
  221.  }
  222.  
  223.  
  224. void pastein(implane *gross,
  225.              dim xpos,dim xw,
  226.              dim ypos,dim yh,
  227.              implane *klein, enum TURNS ori)
  228.  {
  229.   switch (ori)
  230.    {
  231.     case T_NONE: pastequer(gross,xpos+(xw-klein->iwidth)/2,ypos+(yh-klein->iheight)/2,klein);
  232.                  break;
  233.     case T_LEFT: pastelinks(gross,xpos+(xw-klein->iheight)/2,ypos+(yh-klein->iwidth)/2,klein);
  234.                  break;
  235.     case T_RIGHT:pasterechts(gross,xpos+(xw-klein->iheight)/2,ypos+(yh-klein->iwidth)/2,klein);
  236.                  break;
  237.     case T_HEAD: pastehead(gross,xpos+(xw-klein->iwidth)/2,ypos+(yh-klein->iheight)/2,klein);
  238.                  break;
  239.     case T_AUTO:
  240.     default: error(E_INTERN);
  241.    }
  242.  }
  243.  
  244.  
  245.  
  246.  
  247. #define cro(p,d) {if(p) {p->im+=d*p->mwidth; p->iheight-=d;}}
  248. #define cru(p,d) {if(p) {p->iheight-=d;}}
  249. #define crl(p,d) {if(p) {p->im+=d; p->iwidth-=d;}}
  250. #define crr(p,d) {if(p) {p->iwidth-=d;}}
  251.  
  252. void cropit(sizeinfo *si,implane *l,implane *c1,implane *c2)
  253.  {dim x,y,s,w,h;
  254.   sINT nl,nr,no,nu;
  255.  
  256.   uBYTE *ptr;
  257.  
  258.   melde("crop\n");
  259.  
  260.   if(si->imvlen || si->imhlen) error(E_INTERN);
  261.   w=si->rdhlen;
  262.   h=si->rdvlen;
  263.  
  264.   if((!l) || (l->iwidth != w) || (l->iheight != h)) error(E_INTERN);
  265.   
  266.   if(!monochrome)
  267.    {if((!c1) || (c1->iwidth != w) || (c1->iheight != h)) error(E_INTERN);
  268.     if((!c2) || (c2->iwidth != w) || (c2->iheight != h)) error(E_INTERN);
  269.    }
  270.  
  271.  
  272.   for(y=0,no=0;y<h;y++,no++)
  273.    {for(x=0,ptr=(l->im)+y*(l->mwidth); x<w && (*ptr)<MAX_BLACK ;x++,ptr++);
  274.     if(x<w) break;
  275.    }
  276.   cro(l ,no);
  277.   cro(c1,no);
  278.   cro(c2,no);
  279.   h-=no;
  280.  
  281.  
  282.   for(y=h-1,nu=0;y;y--,nu++)
  283.    {for(x=0,ptr=(l->im)+y*(l->mwidth); x<w && (*ptr)<MAX_BLACK ;x++,ptr++);
  284.     if(x<w) break;
  285.    }
  286.   cru(l ,nu);
  287.   cru(c1,nu);
  288.   cru(c2,nu);
  289.   h-=nu;
  290.  
  291.  
  292.   s=l->mwidth;
  293.  
  294.   for(x=0,nl=0;x<w;x++,nl++)
  295.    {for(y=0,ptr=(l->im)+x; y<h && (*ptr)<MAX_BLACK ; y++, ptr+=s);
  296.     if(y<h) break;
  297.    }
  298.   crl(l ,nl);
  299.   crl(c1,nl);
  300.   crl(c2,nl);
  301.   w-=nl;
  302.   
  303.  
  304.   for(x=w-1,nr=0;x;x--,nr++)
  305.    {for(y=0,ptr=(l->im)+x; y<h && (*ptr)<MAX_BLACK ; y++, ptr+=s);
  306.     if(y<h) break;
  307.    }
  308.   crr(l ,nr);
  309.   crr(c1,nr);
  310.   crr(c2,nr);
  311.   w-=nr;
  312.   
  313.   if (do_melde) 
  314.    {
  315.     if (no || nu || nr || nl )
  316.       fprintf(stderr,"Cut off %d top, %d bottom, %d left, %d right,  new size is %ldx%ld\n",
  317.               no,nu,nl,nr,w,h);
  318.     else
  319.       fprintf(stderr,"Nothing cut off\n");
  320.    }
  321.  
  322.   si->imvlen=h;
  323.   si->imhlen=w;
  324.  }
  325.  
  326.  
  327.  
  328.  
  329.  
  330.  
  331.  
  332.  
  333.  
  334.  
  335.  
  336.  
  337.  
  338.  
  339.  
  340. void shrink(sizeinfo *si,implane *l,implane *c1,implane *c2)
  341.  {dim w,h;
  342.  
  343.   melde("shrink\n");
  344.  
  345.   w=si->rdhlen;
  346.   h=si->rdvlen;
  347.  
  348.   if((!l) || (l->iwidth != w) || (l->iheight != h)) error(E_INTERN);
  349.   
  350.   if(!monochrome)
  351.    {if((!c1) || (c1->iwidth != w) || (c1->iheight != h)) error(E_INTERN);
  352.     if((!c2) || (c2->iwidth != w) || (c2->iheight != h)) error(E_INTERN);
  353.    }
  354.  
  355.   if((!si->imvlen) && (!si->imhlen))  /* no subrectangle given */
  356.    {si->imvlen=si->rdvlen;
  357.     si->imhlen=si->rdhlen;
  358.     return;
  359.    }
  360.  
  361.   if (si->imvlen>h || si->imvlen<1 )       error(E_INTERN);
  362.   if (si->imvoff> si->rdvlen - si->imvlen) error(E_INTERN);
  363.  
  364.   if (si->imhlen>w || si->imhlen<1 ) error(E_INTERN);
  365.   if (si->imhoff> si->rdhlen - si->imhlen) error(E_INTERN);
  366.  
  367.   cro(l ,si->imvoff);
  368.   cro(c1,si->imvoff);
  369.   cro(c2,si->imvoff);
  370.  
  371.   cru(l ,si->rdvlen - si->imvoff - si->imvlen);
  372.   cru(c1,si->rdvlen - si->imvoff - si->imvlen);
  373.   cru(c2,si->rdvlen - si->imvoff - si->imvlen);
  374.   
  375.   crl(l ,si->imhoff);
  376.   crl(c1,si->imhoff);
  377.   crl(c2,si->imhoff);
  378.  
  379.   crr(l ,si->rdhlen - si->imhoff - si->imhlen);
  380.   crr(c1,si->rdhlen - si->imhoff - si->imhlen);
  381.   crr(c2,si->rdhlen - si->imhoff - si->imhlen);
  382.   
  383.  
  384.  }
  385.  
  386.  
  387.  
  388. /* Test Data types for their size an whether they 
  389.    are signed / unsigned */
  390.  
  391. void typecheck(void)
  392.  { sBYTE sbyte;
  393.    uBYTE ubyte;
  394.    sINT  sint;
  395.    uINT  uint;
  396.  
  397.  
  398.    if(sizeof(sBYTE) != 1) error(E_CONFIG);
  399.    sbyte=126; sbyte++; sbyte++;
  400.    if(sbyte > 126 ) error(E_CONFIG);
  401.  
  402.    if(sizeof(uBYTE) != 1) error(E_CONFIG);
  403.    ubyte=126; ubyte++; ubyte++;
  404.    if(ubyte < 126 ) error(E_CONFIG);
  405.  
  406. #ifdef U_TOO_LONG
  407.    if(sizeof(sINT) < 4) error(E_CONFIG);
  408.    if(sizeof(uINT) < 4) error(E_CONFIG);
  409. #else
  410.    if(sizeof(sINT) != 4) error(E_CONFIG);
  411.    if(sizeof(uINT) != 4) error(E_CONFIG);
  412. #endif
  413.  
  414.    sint=1; sint--; sint--;
  415.    if(sint>1) error(E_CONFIG);
  416.  
  417.    uint=1; uint--; uint--;
  418.    if(uint<1) error(E_CONFIG);
  419.  
  420.  }
  421.  
  422.